package com.yxy.service.impl;

import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.yxy.common.PageResult;
import com.yxy.constant.StatusConstant;
import com.yxy.context.BaseContext;
import com.yxy.mapper.RemarkMapper;
import com.yxy.mapper.RouteMapper;
import com.yxy.mapper.UserMapper;
import com.yxy.pojo.dto.RouteDTO;
import com.yxy.pojo.dto.RoutePageQueryDTO;
import com.yxy.pojo.dto.RoutePraiseDTO;
import com.yxy.pojo.entity.*;
import com.yxy.pojo.vo.RoutePageQueryVO;
import com.yxy.pojo.vo.RoutePraisePageQueryVO;
import com.yxy.pojo.vo.RoutePraiseVO;
import com.yxy.pojo.vo.RouteVO;
import com.yxy.service.RouteService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.List;

@Service
public class RouteServiceImpl implements RouteService {

    @Autowired
    private RouteMapper routeMapper;
    @Autowired
    private UserMapper userMapper;
    @Autowired
    private RemarkMapper remarkMapper;

    /**
     * 获取所有地理信息
     * @return
     */
    @Override
    public List<Geography> getGeography() {
        return routeMapper.selectAllGeography();
    }

    /**
     * 分页查询
     * @param routePageQueryDTO
     * @return
     */
    @Override
    public PageResult pageQuery(RoutePageQueryDTO routePageQueryDTO) {
        // 查询所有地理信息
        List<Geography> voList = routeMapper.selectAllGeography();

        PageHelper.startPage(routePageQueryDTO.getPage(), routePageQueryDTO.getPageSize());
        Page<RoutePageQueryVO> page = routeMapper.pageQuery(routePageQueryDTO);
        page.forEach(item -> {
            // 地理位置进行转换
            for (Geography vo : voList) {
                if (vo.getId() == item.getGeographyId()) {
                    item.setGeographyType(vo.getType());
                    break;
                }
            }
            if(item.getCreateUser() == StatusConstant.ROUTE_ADMIN_PUBLISH){
                // 创建人-1一律为管理员
                item.setNickName("管理员");
            }else{
                // 用户本身
                User user = userMapper.selectById(item.getCreateUser());
                item.setAvatar(user.getAvatar());
                item.setNickName(user.getName());
            }
            // 查询评论量
            List<Remark> remarkList = remarkMapper.selectCountByTypeAndTypeId(item.getId(), "route");
            item.setRemarkCount(remarkList.size());
        });
        return new PageResult(page.getTotal(), page.getResult());
    }

    /**
     * 新增
     * @param routeDTO
     */
    @Override
    public void add(RouteDTO routeDTO) {
        Route route = Route.builder()
                .name(routeDTO.getName())
                .temperature(routeDTO.getTemperature())
                .geographyId(routeDTO.getGeographyId())
                .cover(routeDTO.getCover())
                .introduce(routeDTO.getIntroduce())
                .detail(routeDTO.getDetail())
                .createTime(LocalDateTime.now())
                .createUser(routeDTO.getPersonType())
                .build();
        routeMapper.insert(route);
    }

    /**
     * 批量删除
     * @param ids
     */
    @Transactional
    @Override
    public void batchDelete(List<Integer> ids) {
        routeMapper.deleteByIds(ids);
        // 删除线路对应的点赞记录
        routeMapper.deletePraiseByIds(ids);
    }

    /**
     * 修改
     * @param routeDTO
     */
    @Override
    public void update(RouteDTO routeDTO) {
        Route route = Route.builder()
                .id(routeDTO.getId())
                .name(routeDTO.getName())
                .temperature(routeDTO.getTemperature())
                .geographyId(routeDTO.getGeographyId())
                .cover(routeDTO.getCover())
                .introduce(routeDTO.getIntroduce())
                .views(routeDTO.getViews())
                .praise(routeDTO.getPraise())
                .detail(routeDTO.getDetail())
                .updateTime(LocalDateTime.now())
                .updateUser(BaseContext.getCurrentId())
                .build();
        routeMapper.update(route);
    }

    /**
     * 根据id查询
     * @param id
     * @return
     */
    @Override
    public RouteVO getRouteById(int id) {
        Route route = routeMapper.selectById(id);
        RouteVO routeVO = new RouteVO();
        BeanUtils.copyProperties(route, routeVO);
        // 查询地理信息
        List<Geography> voList = routeMapper.selectAllGeography();
        for (Geography vo : voList){
            if(route.getGeographyId() == vo.getId()){
                routeVO.setGeographyType(vo.getType());
            }
        }
        // 发布人信息
        if(route.getCreateUser() == StatusConstant.ROUTE_ADMIN_PUBLISH){
            // 创建人-1一律为管理员
            routeVO.setNickName("管理员");
        }else{
            // 用户本身
            User user = userMapper.selectById(route.getCreateUser());
            routeVO.setAvatar(user.getAvatar());
            routeVO.setNickName(user.getName());
        }
        return routeVO;
    }

    /**
     * 添加浏览量
     * @param id
     * @param views
     */
    @Override
    public void addRouteViews(int id, int views) {
        routeMapper.addRouteViews(id, views);
    }

    /**
     * 判断是否点赞
     * @param userId
     * @param routeId
     * @return
     */
    @Override
    public RoutePraiseVO isPraise(int userId, int routeId) {
        RoutePraise routePraise = routeMapper.isPraise(userId, routeId);
        // 若查询为空，则用户第一次进入
        if(routePraise == null){
            // 进行添加操作，值为0（未点赞）
            routeMapper.addPraise(RoutePraise.builder()
                    .userId(userId)
                    .routeId(routeId)
                    .isPraise(StatusConstant.PRAISE_CANCEL)
                    .build());
            return RoutePraiseVO.builder().idPraise(StatusConstant.PRAISE_CANCEL).build();
        }
        return RoutePraiseVO.builder().idPraise(routePraise.getIsPraise()).build();
    }

    /**
     * 修改点赞状态
     * @param routePraiseDTO
     */
    @Transactional
    @Override
    public void updatePraise(RoutePraiseDTO routePraiseDTO) {
        // 修改状态
        routeMapper.updatePraise(RoutePraise.builder()
                .routeId(routePraiseDTO.getRouteId())
                .userId(routePraiseDTO.getUserId())
                .isPraise(routePraiseDTO.getIsPraise())
                .build());
        // 判断是加还是减
        int praise = routePraiseDTO.getIsPraise() == StatusConstant.PRAISE_OK ? 1 : -1;
        // 获取线路的点赞量
        Route route = routeMapper.selectById(routePraiseDTO.getRouteId());
        // 修改线路信息中的点赞量
        routeMapper.update(Route.builder()
                .id(routePraiseDTO.getRouteId())
                .praise(route.getPraise() + praise)
                .build());
    }

    /**
     * 获取线路点赞量
     * @param routePageQueryDTO
     * @return
     */
    @Override
    public PageResult pageQueryRoutePraise(RoutePageQueryDTO routePageQueryDTO) {
        PageHelper.startPage(routePageQueryDTO.getPage(), routePageQueryDTO.getPageSize());
        Page<RoutePraisePageQueryVO> page = routeMapper.pageQueryRoutePraise(routePageQueryDTO);
        page.getResult().forEach(item -> {
            // 查询线路信息
            Route route = routeMapper.selectById(item.getRouteId());
            item.setCover(route.getCover());
            item.setName(route.getName());
            item.setPraise(route.getPraise());
            item.setViews(route.getViews());
            // 查询评论量
            List<Remark> remarkList = remarkMapper.selectCountByTypeAndTypeId(item.getId(), "route");
            item.setRemarkCount(remarkList.size());
            if(route.getCreateUser() == StatusConstant.ROUTE_ADMIN_PUBLISH){
                // 创建人-1一律为管理员
                item.setNickName("管理员");
            }else{
                // 用户本身
                User user = userMapper.selectById(route.getCreateUser());
                item.setAvatar(user.getAvatar());
                item.setNickName(user.getName());
            }
        });
        return new PageResult(page.getTotal(), page.getResult());
    }
}
